//
//  QSFileManager.swift
//  TestSwift
//
//  Created by Song on 2018/5/18.
//  Copyright © 2018年 Song. All rights reserved.
//

import UIKit

/// 文件路径类型
enum QSPathType {
    case document
    case cache
    case unKnown
}

/// 文件内容类型
enum QSFileContentType {
    case array
    case dictionary
    case string
    case data
}

class QSFileManager: NSObject {
    /// 获取Document路径
    class func qs_getDocumentPath() -> String{
        let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
        let path = paths.first
        
        return path!
    }
    
    /// 获取Cache路径
    class func qs_getCachePath() -> String{
        let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.cachesDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
        let path = paths.first
        
        return path!
    }
    
    /// 创建文件夹
    ///
    /// - Parameters:
    ///   - pathType: 放在哪个路径下，Document或Cache，默认 unKnown
    ///   - directoryName: 文件夹名，可以一个文件夹名，也可以传一个路径，如果pathType为unKnown，需要传入完整路径
    /// - Returns: 成功：返回文件夹路径；失败：返回nil
    class func qs_createDirectory(in pathType: QSPathType = .unKnown, directoryName: String) -> String? {
        // 获取路径
        var path = String.init()
        switch pathType {
        case .document:
            path = self.qs_getDocumentPath()
        case .cache:
            path = self.qs_getCachePath()
        case .unKnown:
            path = directoryName
        }
        
        // 创建文件管理者
        let fileManger = FileManager.default
        // 创建文件夹
        if !directoryName.hasPrefix("/") {
            path.append("/")
        }
        let directoryPath = path + directoryName
        
        do {
            try fileManger.createDirectory(atPath: directoryPath, withIntermediateDirectories: true, attributes: nil)
            #if DEBUG
            debugPrint("文件夹创建成功")
            #endif
            
            return directoryPath
        } catch let error {
            #if DEBUG
            debugPrint(error.localizedDescription)
            debugPrint("文件夹创建失败")
            #endif
            
            return nil
        }
    }
    
    /// 创建文件
    ///
    /// - Parameters:
    ///   - pathType: 放在哪个路径下，Document或Cache，默认 unKnown
    ///   - fileName: 文件名，可以一个文件名，也可以传一个路径，如果pathType为unKnown，需要传入完整路径
    /// - Returns: 成功：返回文件路径；失败：返回nil
    class func qs_createFile(in pathType: QSPathType = .unKnown, fileName: String) -> String? {
        // 获取路径
        var path = String.init()
        switch pathType {
        case .document:
            path = self.qs_getDocumentPath()
        case .cache:
            path = self.qs_getCachePath()
        case .unKnown:
            path = fileName
        }
        
        // 创建文件管理者
        let fileManger = FileManager.default
        // 文件路径
        if !fileName.hasPrefix("/") {
            path.append("/")
        }
        let filePath = path + fileName
        
        // 先判断是否存在  不存在再创建
        if !fileManger.fileExists(atPath: filePath) {
            let isSuccess = fileManger.createFile(atPath: filePath, contents: nil, attributes: nil)
            
            if isSuccess {
                #if DEBUG
                debugPrint("文件创建成功")
                #endif
                return filePath
            }else {
                #if DEBUG
                debugPrint("文件创建失败")
                #endif
                return nil
            }
        }
        
        return filePath
    }
    
    /// 把数据写入文件
    ///
    /// - Parameters:
    ///   - pathType: 放在哪个路径下，Document或Cache，默认 unKnown
    ///   - data: 要写入的数据
    ///   - fileName: 文件名，可以一个文件名，也可以传一个路径，如果pathType为unKnown，需要传入完整路径
    /// - Returns: 是否写入成功
    class func qs_writeToFile(in pathType: QSPathType = .unKnown, data: AnyObject, fileName: String) -> Bool {
        // 获取路径
        var path = String.init()
        switch pathType {
        case .document:
            path = self.qs_getDocumentPath()
        case .cache:
            path = self.qs_getCachePath()
        case .unKnown:
            path = fileName
        }
        
        // 文件路径
        if !fileName.hasPrefix("/") {
            path.append("/")
        }
        let filePath = path + fileName
        
        return data.write(toFile: filePath, atomically: true)
    }
    
    /// 读取文件内容
    ///
    /// - Parameters:
    ///   - pathType: 放在哪个路径下，Document或Cache，默认 unKnown
    ///   - contentType: 文件内容的类型，默认 string
    ///   - fileName: 文件名，可以一个文件名，也可以传一个路径，如果pathType为unKnown，需要传入完整路径
    /// - Returns: 返回文件中数据，拿不到数据返回nil
    class func qs_readFromFile(in pathType: QSPathType = .unKnown, contentType: QSFileContentType = .string, fileName: String) -> AnyObject? {
        // 获取路径
        var path = String.init()
        switch pathType {
        case .document:
            path = self.qs_getDocumentPath()
        case .cache:
            path = self.qs_getCachePath()
        case .unKnown:
            path = fileName
        }
        
        // 文件路径
        if !fileName.hasPrefix("/") {
            path.append("/")
        }
        let filePath = path + fileName
        
        switch contentType {
        case .array:
            return NSArray.init(contentsOfFile: filePath)
            
        case .dictionary:
            return NSDictionary.init(contentsOfFile: filePath)
            
        case .string:
            return try? String.init(contentsOfFile: filePath, encoding: String.Encoding.utf8) as AnyObject
            
        case .data:
            return try? NSData.init(contentsOfFile: filePath) as AnyObject
        }
    }
    
    /// 删除文件
    ///
    /// - Parameters:
    ///   - pathType: 放在哪个路径下，Document或Cache，默认 unKnown
    ///   - fileName: 文件名，可以一个文件名，也可以传一个路径，如果pathType为unKnown，需要传入完整路径
    /// - Returns: 是否删除成功
    class func qs_deleteFile(in pathType: QSPathType = .unKnown, fileName: String) -> Bool {
        // 获取路径
        var path = String.init()
        switch pathType {
        case .document:
            path = self.qs_getDocumentPath()
        case .cache:
            path = self.qs_getCachePath()
        case .unKnown:
            path = fileName
        }
        
        // 创建文件管理者
        let fileManger = FileManager.default
        // 文件路径
        if !fileName.hasPrefix("/") {
            path.append("/")
        }
        let filePath = path + fileName
        
        // 先判断是否存在
        if !fileManger.fileExists(atPath: filePath) {
            #if DEBUG
            debugPrint("文件不存在")
            #endif
            return true
        } else {
            do {
                try fileManger.removeItem(atPath: filePath)
                #if DEBUG
                debugPrint("删除成功")
                #endif
                return true
            } catch {
                #if DEBUG
                debugPrint("删除失败")
                #endif
                return false
            }
        }
    }
    
    /// 获取文件的大小
    ///
    /// - Parameter filePath: 完整的文件路径
    /// - Returns: 文件大小(KB)
    class func qs_getFileSize(_ filePath: String) -> Double {
        let fileManger = FileManager.default
        // 判断文件是否存在
        guard fileManger.fileExists(atPath: filePath) else {
            return 0
        }
        
        let attr = try! fileManger.attributesOfItem(atPath: filePath)
        let fileSize = Double((attr as NSDictionary).fileSize())
        
        return fileSize/1024
    }
}
